﻿using System;
using System.IO;
using System.Threading;
using System.Windows.Forms;
using System.Xml;
using System.Text.RegularExpressions;

namespace RegularConfig
{
    public partial class FormMain : Form
    {
        public FormMain()
        {
            InitializeComponent();
            btnTest.Enabled = false;
            btnSave.Enabled = false;
        }
        string filepath = AppDomain.CurrentDomain.BaseDirectory.Replace("\\bin\\Debug", "") + "Rules\\";
        XmlDocument doc = null;
        private void FormMain_Load(object sender, EventArgs e)
        {
            DirectoryInfo info = new DirectoryInfo(filepath);
            var files = info.GetFiles("*.xml");

            foreach (var file in files)
            {
                cbxRules.Items.Add(file.Name);
            }
            if (cbxRules.Items.Count > 0)
                cbxRules.SelectedIndex = 0;
        }

        private void btnLoad_Click(object sender, EventArgs e)
        {
            cbxRules.Enabled = false;
            btnLoad.Enabled = false;
            btnTest.Enabled = true;
            btnSave.Enabled = true;

            doc = new XmlDocument();
            doc.Load(filepath + cbxRules.SelectedItem.ToString());
            listBoxRule.Items.Clear();
            foreach (XmlNode node in doc.SelectSingleNode("RuleConfigInfo").ChildNodes)
            {

                listBoxRule.Items.Add(node.Name);
            }
        }

        private void btnSave_Click(object sender, EventArgs e)
        {
            cbxRules.Enabled = true;
            btnLoad.Enabled = true;
            btnTest.Enabled = false;
            btnSave.Enabled = false;

            doc.Save(filepath + cbxRules.SelectedItem);
            listBoxRule.Items.Clear();
        }

        private void listBoxRule_SelectedIndexChanged(object sender, EventArgs e)
        {
            foreach (XmlNode node in doc.SelectSingleNode("RuleConfigInfo/" + listBoxRule.SelectedItem).ChildNodes)
            {

                switch (node.Name)
                {
                    case "RegexName":
                        txtDesc.Text = node.InnerText;
                        break;
                    case "Pattern":
                        txtPatter.Text = node.InnerText;
                        break;
                    case "Variable":
                        //txtVariable.Text = node.InnerText;
                        break;
                    case "FilterPattern":
                        txtReplace.Text = node.InnerText;
                        break;
                    default:
                        break;
                }
            }
        }

        private void txt_KeyUp(object sender, KeyEventArgs e)
        {
            foreach (XmlNode node in doc.SelectSingleNode("RuleConfigInfo/" + listBoxRule.SelectedItem).ChildNodes)
            {
                switch (node.Name)
                {
                    case "RegexName":
                        node.InnerText = txtDesc.Text;
                        break;
                    case "Pattern":
                        node.InnerText = txtPatter.Text;
                        break;
                    case "Variable":
                        node.InnerText = "";// txtVariable.Text;
                        break;
                    case "FilterPattern":
                        node.InnerText = txtReplace.Text;
                        break;
                    default:
                        break;
                }
            }
        }

        private void btnTest_Click(object sender, EventArgs e)
        {
            FormTest formTest = new FormTest();
            txtResult = formTest.txtResult;
            Thread thread1 = new Thread(new ParameterizedThreadStart(btnDo_Work));
            thread1.Start();

            formTest.ShowDialog(this);
        }

        private void btnDo_Work(object obj)
        {
            try
            {
                string Pattern = string.Empty;
                string Variable = string.Empty;
                string FilterPattern = string.Empty;

                string url = string.Empty;
                string HtmlContent = string.Empty;

                MatchCollection Matchs = null;

                UpdateLabel("========采集开始=========");
                // 1.
                Pattern = getXmlValue(Regular.ListUrl, RegularItems.Pattern);
                //Variable = getXmlValue(Regular.ListUrl, RegularItems.Variable);
                //FilterPattern = getXmlValue(Regular.ListUrl, RegularItems.FilterPattern);

                HtmlContent = MyHttpClient.Get(Pattern,1000);
                UpdateLabel("获得" + Pattern);

                // 2.
                Pattern = getXmlValue(Regular.GetUrlKey, RegularItems.Pattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                foreach (Match item in Matchs)
                {
                    // 3.
                    Pattern = getXmlValue(Regular.Url, RegularItems.Pattern);
                    url = Pattern.Replace("{UrlKey}", item.Groups[1].Value);
                    //HtmlContent = Tools.HttpClient.Get(url,null);
                    UpdateLabel("匹配到" + url);

                    // 4.
                }

                // 4.
                UpdateLabel("采集" + url);
                HtmlContent = MyHttpClient.Get(url, 1000);


                Pattern = getXmlValue(Regular.Name, RegularItems.Pattern);
                FilterPattern = getXmlValue(Regular.Name, RegularItems.FilterPattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                string _name = string.Empty;
                foreach (Match item in Matchs)
                {
                    _name = HandlerReplace(item.Groups[1].Value, FilterPattern);
                    UpdateLabel(Regular.Name + "-->" + _name);
                }

                // 5.
                Pattern = getXmlValue(Regular.State, RegularItems.Pattern);
                FilterPattern = getXmlValue(Regular.State, RegularItems.FilterPattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                _name = string.Empty;
                foreach (Match item in Matchs)
                {
                    _name = HandlerReplace(item.Groups[1].Value, FilterPattern);
                    UpdateLabel(Regular.State + "-->" + _name);
                }

                // 6.
                Pattern = getXmlValue(Regular.Img, RegularItems.Pattern);
                FilterPattern = getXmlValue(Regular.Img, RegularItems.FilterPattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                _name = string.Empty;
                foreach (Match item in Matchs)
                {
                    _name = HandlerReplace(item.Groups[1].Value, FilterPattern);
                    UpdateLabel(Regular.Img + "-->" + _name);
                }

                // 7.
                Pattern = getXmlValue(Regular.Tag, RegularItems.Pattern);
                FilterPattern = getXmlValue(Regular.Tag, RegularItems.FilterPattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                _name = string.Empty;
                foreach (Match item in Matchs)
                {
                    _name = HandlerReplace(item.Groups[1].Value, FilterPattern);
                    UpdateLabel(Regular.Tag + "-->" + _name);
                }

                // 8.
                Pattern = getXmlValue(Regular.Category, RegularItems.Pattern);
                FilterPattern = getXmlValue(Regular.Category, RegularItems.FilterPattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                _name = string.Empty;
                foreach (Match item in Matchs)
                {
                    _name = HandlerReplace(item.Groups[1].Value, FilterPattern);
                    UpdateLabel(Regular.Category + "-->" + _name);
                }

                // 9.
                Pattern = getXmlValue(Regular.Contents, RegularItems.Pattern);
                FilterPattern = getXmlValue(Regular.Contents, RegularItems.FilterPattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                _name = string.Empty;
                foreach (Match item in Matchs)
                {
                    _name = HandlerReplace(item.Groups[1].Value, FilterPattern);
                    UpdateLabel(Regular.Contents + "-->" + _name);
                }

                //10 
                Pattern = getXmlValue(Regular.Intro, RegularItems.Pattern);
                FilterPattern = getXmlValue(Regular.Intro, RegularItems.FilterPattern);
                Matchs = Regex.Matches(HtmlContent, Pattern);
                _name = string.Empty;
                foreach (Match item in Matchs)
                {
                    _name = HandlerReplace(item.Groups[1].Value, FilterPattern);
                    UpdateLabel(Regular.Intro + "-->" + _name);
                }
            }
            catch (Exception ex)
            {
                UpdateLabel(ex.Message);
            }
            finally
            {
                Thread.CurrentThread.Abort();
            }

        }

        TextBox txtResult = null;
        private void UpdateLabel(object str)
        {
            if (txtResult.InvokeRequired)
            {
                // 当一个控件的InvokeRequired属性值为真时，说明有一个创建它以外的线程想访问它
                Action<string> actionDelegate = (x) =>
                {
                    this.txtResult.Text += x.ToString() + Environment.NewLine;
                    txtResult.SelectionStart = txtResult.Text.Length;
                    txtResult.ScrollToCaret();
                };
                txtDesc.Invoke(actionDelegate, str);

            }
            else
            {
                txtResult.Text += str.ToString();
            }

        }

        string getXmlValue(Regular root, RegularItems item)
        {
            return doc.SelectSingleNode("RuleConfigInfo/" + root + "/" + item).InnerText;
        }

        string HandlerReplace(string Val, string FilterPatter)
        {
            string[] filterArray = FilterPatter.Split(Environment.NewLine.ToCharArray());
            foreach (var filter in filterArray)
            {
                if (!filter.Contains("|")) continue;
                var replaceArray = filter.Split('|');
                Val= Regex.Replace(Val, replaceArray[0], replaceArray[1]);
            }
            return Val;
        }
    }

    enum Regular
    {
        SiteName,
        SiteCharset,
        ListUrl,
        GetUrlKey,
        Url,
        Name,
        State,
        Img,
        Tag,
        Category,
        Contents,
        Intro
    }
    enum RegularItems
    {
        RegexName,
        Pattern,
        Variable,
        FilterPattern
    }

}
